package at.ac.tuwien.ame

import com.google.common.base.Predicate
import org.eclipse.core.resources.IProject
import org.eclipse.emf.ecore.EClass
import org.eclipse.emf.ecore.EClassifier
import org.eclipse.emf.ecore.EOperation
import org.eclipse.emf.ecore.EPackage
import org.eclipse.emf.ecore.resource.Resource

/**
 * Contains several utility methods for FTL.
 */
class FTLUtils {
	/**
	 * Returns the package of a full-qualified class name.
	 */
	def static getPackage(String str) {
		str.substring(0, Math::max(0, str.lastIndexOf('.')))
	}

	/**
	 * Returns the unqualified name of a full-qualified class name.
	 */
	def static getUnqualifiedName(String str) {
		str.substring(str.lastIndexOf('.') + 1)
	}

	/**
	 * Loads the corresponding Java {@link Class} for the given {@link EClassifier}.
	 */
	def static getClass(EClassifier classifier) {
		val sb = new StringBuilder(classifier.name)
		var container = classifier.eContainer as EPackage
		while (container != null) {
			sb.insert(0, '.').insert(0, container.name)
			container = container.ESuperPackage
		}
		Class::forName(sb.toString)
	}
	
	/**
	 * Loads the {@link EClass} with the given name from the provided XMI {@link Resource}.
	 */
	def static EClass classForName(Resource resource, String element) {
		val className = getUnqualifiedName(element)
		for (EClass clazz : resource.allContents.toIterable.filter(typeof(EClass))) {
			if (clazz.name.endsWith(className)) {
				return clazz
			}
		}
		null
	}
}

/**
 * Checks whether an {@link EOperation} matches the given signature.
 */
class EOperationPredicate implements Predicate<EOperation> {
	val String name

	new(String name) {
		this.name = name.replaceFirst("\\(.+", "")
	}

	override apply(EOperation input) {
		return input.name.equals(name)
	}
}

/**
 * Filters {@link IProject}s, which contain models.
 */
class EcoreModelProjectPredicate implements Predicate<IProject> {
	override apply(IProject input) {
		input.open && input.getFolder("model").exists
	}
}
